import DefensiveFacility from "../facility/DefensiveFacility";
import DestructibleFacility from "../facility/DestructibleFacility";
import LaunchableFalicity from "../facility/LaunchableFalicity";
import Mine from "../facility/pulbicFacility/Mine";
import DrawingBoard from "../funcObj/DrawingBoard";
import { Location, MapLength, blockSize, pixelLength } from "../info/Predefine";
import GameManager from "../manager/GameManager";
import PlayerManager from "../manager/PlayerManager";
import Player from "../player/Player";

const { ccclass, property } = cc._decorator;

@ccclass
export default class UiMiniMap extends cc.Component {

    private minimapTexture: cc.RenderTexture;

    public static instance: UiMiniMap = null;

    @property(cc.Sprite)
    minimapSprite: cc.Sprite = null;

    @property(cc.Camera)
    camera: cc.Camera = null;

    @property(cc.Node)
    shotRangeNode: cc.Node = null;

    db: DrawingBoard = null;

    private timing: number = 0;

    protected onLoad(): void {
        UiMiniMap.instance = this;
    }

    start() {
        this.minimapTexture = new cc.RenderTexture();
        this.minimapTexture.initWithSize(240, 240);
        this.db = new DrawingBoard(this.node.width, this.node.height);
        //设置画板的绘图颜色（每次绘制前都可以重新设置）
        this.db.setColor(255, 0, 0, 255);
        //设置画板绘制的线条的宽度
        this.shotRangeNode.active = false;
        let spriteFrame = new cc.SpriteFrame(this.minimapTexture);
        this.minimapSprite.spriteFrame = spriteFrame;

    }

    update(dt) {
        switch (this.timing) {
            case 0:
                //显示矿
                this.db.clear();
                this.showMineArrayItem(GameManager.instance.mineArray);
                this.timing++;
                break;
            case 1:
                //显示设施
                PlayerManager.instance.playerParent.getComponentsInChildren(Player).forEach((p: Player) => {
                    p.facilityArr.forEach((arr, index) => this.showFacilityArrayItem(arr, p === PlayerManager.instance.controllerPlayer))
                })
                this.timing++;
                break;
            case 2:
                //显示飞行物
                this.showFlyer();
                this.timing++;
                break;
            case 3:
                this.showViewRect();
                this.minimapTexture.initWithData(this.db.getData(), cc.Texture2D.PixelFormat.RGBA8888, this.db.width, this.db.height);
                this.timing = 0;
                break;
        }
    }

    showViewRect() {
        this.db.setLineWidth(1);
        this.db.setLineCircleEnd(false);
        this.db.setColor(255, 255, 0);

        let screenWidth = cc.view.getVisibleSize().width;
        let screenHeight = cc.view.getVisibleSize().height;

        // 获取摄像机的缩放比例
        let zoomRatio = this.camera.zoomRatio;

        // 计算视口的宽度和高度
        let viewportWidth = screenWidth / zoomRatio;
        let viewportHeight = screenHeight / zoomRatio;

        let rate = 6400 / 240;
        let position = this.camera.node.position.sub(cc.v3(viewportWidth / 2, -(viewportHeight / 2))).add(cc.v3(3200, 3200)).mulSelf(1 / rate);
        position.y = 240 - position.y;

        let width = viewportWidth / rate;
        let heigth = viewportHeight / rate;
        this.db.line(position.x, position.y, position.x + width, position.y);
        this.db.lineTo(position.x + width, position.y + heigth);
        this.db.lineTo(position.x, position.y + heigth);
        this.db.lineTo(position.x, position.y);
    }

    showMineArrayItem(mineArr: Mine[]) {
        this.db.setLineWidth(3);
        this.db.setColor(255, 255, 255);

        for (let i = 0; i < mineArr.length; i++) {
            let location = mineArr[i].locations[0];
            if (!mineArr[i].node) {
                cc.log("error")
            }
            if (PlayerManager.instance.controllerPlayer.isLocationVisible(location)) {
                this.db.drawRect(location.locationX * 3, location.locationY * 3, 3, 3);
            }
        }
    }

    showFacilityArrayItem(arr: DestructibleFacility[], isControlPlayer: boolean) {
        this.db.setLineWidth(3);
        if (isControlPlayer) {
            this.db.setColor(0, 255, 0);
        } else {
            this.db.setColor(255, 0, 0);
        }

        for (let i = 0; i < arr.length; i++) {
            let locaitons = arr[i].locations;
            locaitons = locaitons.filter(loca => PlayerManager.instance.controllerPlayer.isLocationVisible(loca));
            locaitons.forEach(loca =>
                this.db.drawRect(loca.locationX * 3, loca.locationY * 3, 3, 3)
            )
        }
    }

    showFlyer() {
        this.db.setColor(0, 255, 0);
        let nodes = GameManager.instance.aboveFlyerParent.children;
        for (let i = 0; i < nodes.length; i++) {
            let box = nodes[i].getBoundingBox();
            let leftDown = GameManager.instance.getMapLocation(cc.v3(box.xMin, box.yMin));
            let width = Math.ceil(box.width / blockSize);
            let height = Math.ceil(box.height / blockSize);
            this.db.drawRect(leftDown.locationX * 3 + 1, leftDown.locationY * 3 + 1, width * 3, height * 3)
        }
        this.db.setColor(255, 0, 0);
        nodes = GameManager.instance.underFlyerParent.children;
        for (let i = 0; i < nodes.length; i++) {
            let box = nodes[i].getBoundingBox();
            let leftDown = GameManager.instance.getMapLocation(cc.v3(box.xMin, box.yMin));
            let center = GameManager.instance.getMapLocation(box.center)
            if (center.locationX >= 0 && center.locationX < MapLength && center.locationY >= 0 && center.locationY < MapLength && PlayerManager.instance.controllerPlayer.isLocationVisible(center)) {
                let width = Math.ceil(box.width / blockSize);
                let height = Math.ceil(box.height / blockSize);
                this.db.drawRect(leftDown.locationX * 3 + 1, leftDown.locationY * 3 + 1, width, height)
            }
        }
    }

    updateShotRangeUi(location: Location) {
        //如果有射程 在小地图上显示射程范围
        this.shotRangeNode.stopAllActions();
        let newFac = GameManager.instance.getFacilityByLocation(location);
        let shotRange = 0;
        if (newFac && (newFac instanceof DefensiveFacility || newFac instanceof LaunchableFalicity) && newFac.player === PlayerManager.instance.controllerPlayer && PlayerManager.instance.controllerPlayer.isFacilityVisible(newFac)) {
            shotRange = newFac.shotRange * 2 * 3;
            this.shotRangeNode.active = true;
            let position = GameManager.instance.getGamePosition(location);
            let rate = this.node.width / pixelLength;
            this.shotRangeNode.position = position.mulSelf(rate);
            this.shotRangeNode.setContentSize(0, 0);
            cc.tween(this.shotRangeNode)
                .to(0.5, { width: shotRange, height: shotRange })
                .start();
        } else {
            this.shotRangeNode.active = false;
        }
    }

    protected onDestroy(): void {
        UiMiniMap.instance = null;
    }
}
